using System;
using System.Data.SqlClient;
using PropertyExpression.ControllableQuery.TypedReader;

namespace PropertyExpression.ControllableQuery.Test
{
    public static class Materializer
    {
        public static T Materialize<T>(this IDataReader<T> reader)
        {
            return Cache<T>.Func(reader.SqlDataReader);
        }

        private static class Cache<T>
        {
            public static readonly Func<SqlDataReader, T> Func;

            static Cache()
            {
                Func = DynamicMaterializer.Build<SqlDataReader, T>(
                    type => {
                        if (type == typeof (string))
                            return typeof (Materializer).GetMethod("GetString");
                        else if (type == typeof (Guid))
                            return typeof (Materializer).GetMethod("GetGuid");
                        else if (type == typeof(int))
                            return typeof(Materializer).GetMethod("GetInt");
                        else
                            throw new NotImplementedException();
                    });
            }
        }

        public static string GetString(SqlDataReader reader, string fieldName)
        {
            return reader.GetString(reader.GetOrdinal(fieldName));
        }

        public static Guid GetGuid(SqlDataReader reader, string fieldName)
        {
            return reader.GetGuid(reader.GetOrdinal(fieldName));
        }

        public static int GetInt(SqlDataReader reader, string fieldName)
        {
            return reader.GetInt32(reader.GetOrdinal(fieldName));
        }
    }
}